// Kuik end derty R/W lock test
// rp

#include "rwlock.h"
#include <stdio.h>

_linda_rw_lock mylok;
_linda_rw_condition mykon;

int myid;

void reader_loop()
{
  for (;;) {
  printf("R%d proboje dostac blokade\n", myid);
  _linda_lock_reader(&mylok);
  printf("R%d dostal blokade\n", myid);
  sleep(rand() % 5);
  printf("R%d zwalnia blokade\n", myid);
  _linda_release_reader(&mylok);
  sleep(rand() % 5);
  }
}

void writer_loop()
{
  for (;;)
  {
  printf("W%d proboje dostac blokade\n", myid);
  _linda_lock_writer(&mylok);
  printf("W%d dostal blokade\n", myid);
  sleep(rand() % 5);
  printf("W%d zwalnia blokade\n", myid);
  _linda_release_writer(&mylok);
  sleep(rand() % 5);
  }
}

void sig(int u)
{
  printf("%d oddaje blokade\n", myid);
  _linda_leave_rw_lock(&mylok);
  printf("%d oddal blokade\n", myid);
  exit(0);
}

int main(int argc, char* argv[])
{
  char bs[80];
  if (argc < 2) return 1;
  
  srand(time(NULL));
  
  signal(SIGINT, sig);
  switch (argv[1][0])
  {
    case 'c':
      _linda_create_rw_lock("TEST", &mylok);
    break;
    case 'd':
      _linda_get_rw_lock("TEST", &mylok);
      _linda_destroy_rw_lock(&mylok);
      break;
    case 'r':
      _linda_get_rw_lock("TEST", &mylok);
      myid = argv[1][1] - '0';
      reader_loop();
      break;
    case 'w':
      _linda_get_rw_lock("TEST", &mylok);
      myid = argv[1][1] - '0';
      writer_loop();
      break;
    case 'q':
      _linda_get_rw_lock("TEST", &mylok);
      _linda_create_rw_condition(&mylok, "TESTc", &mykon);
      _linda_lock_writer(&mylok);
      printf("q: zablokowano jako pisarz, bede czekal\n");
      _linda_writer_wait_condidion(&mykon, 0);
      printf("q: wybudzony, wpisz cos i nacisnij\n");
      scanf("%s", bs);
      _linda_release_writer(&mylok);
      _linda_destroy_rw_condition(&mykon);
      _linda_leave_rw_lock(&mylok);
      break;
    case 's':
      _linda_get_rw_lock("TEST", &mylok);
      _linda_get_rw_condition(&mylok, "TESTc", &mykon);
      _linda_lock_writer(&mylok);
      printf("s: zablokowano jako pisarz, bede czekal\n");
      _linda_writer_signal_condidion(&mykon);
      printf("s: wybudzony\n");
      _linda_release_writer(&mylok);
      _linda_leave_rw_lock(&mylok);
      break;      
  }
  return 0;
}